package subsystems

import (
	"fmt"
	"io/ioutil"
	"os"
	"path"
	"strconv"
)

// CPU 时间片的比例
type CpuSubSystem struct {
}

func MakeCpuSubSystem() *CpuSubSystem {
	return &CpuSubSystem{}
}

func (this *CpuSubSystem) Name() string {
	return "cpu"
}

func (this *CpuSubSystem) Set(cGroupPath string, resConfigPtr *ResourceConfig) error {
	if subSysCGroupPath, err := GetCGroupPath(this.Name(), cGroupPath, true); err == nil {
		if resConfigPtr.CpuShare != "" {
			if err := ioutil.WriteFile(path.Join(subSysCGroupPath, "cpu.shares"), []byte(resConfigPtr.CpuShare), 0644); err != nil {
				return fmt.Errorf("set cgroup cpu share fail %v", err)
			}
		}
		return nil
	} else {
		return err
	}
}

// Apply 把要限制的进程写入tasks中
func (this *CpuSubSystem) Apply(cGroupPath string, pid int) error {
	if subSysCGroupPath, err := GetCGroupPath(this.Name(), cGroupPath, false); err == nil {
		if err := ioutil.WriteFile(path.Join(subSysCGroupPath, "tasks"), []byte(strconv.Itoa(pid)), 0644); err != nil {
			return fmt.Errorf("apply cpu cgroup proc fail %v", err)
		}
		return nil
	} else {
		return fmt.Errorf("get cgroup %s error: %v", cGroupPath, err)
	}
}

// 删除CPU限制
func (this *CpuSubSystem) Remove(cGroupPath string) error {
	if subSysCGroupPath, err := GetCGroupPath(this.Name(), cGroupPath, false); err == nil {
		return os.RemoveAll(subSysCGroupPath)
	} else {
		return err
	}
}
